<?php
class Main_Db_Adapter_Mysql extends Main_Db_Adapter_Abstract
{
	const FETCH_ASSOC = MYSQL_ASSOC; //1
	
	const FETCH_NUM	= MYSQL_NUM; //2
	
	const FETCH_BOTH = MYSQL_BOTH; //3
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#_connect()
	 */
	protected function _connect() 
	{
		$host = $this->_options['host'] . ':' . $this->_options['port'];
		$dbname = $this->_options['dbname'];
		$username = $this->_options['username'];
		$password = $this->_options['password'];
				
		if (! $this->_connection = mysql_connect($host, $username, $password, true) ) {
    		throw new Exception("Could not connect: " . mysql_error());
		} 	

		if (! mysql_select_db($dbname, $this->_connection)) {
			throw new Exception("Can not select database: " . mysql_error());
		}

		 $this->_fetchMode = self::FETCH_ASSOC;

		 $encoding = Zend_Registry::getInstance()->encoding;
		 
		 $this->query("SET NAMES '{$encoding}'");
		 
		 return true;
	}
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#closeConnection()
	 */
	public function closeConnection()
	{
		$result = ((bool) mysql_close($this->_connection));
		parent::closeConnection();
		return $result;
	}
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#query()
	 */
	public function query($sql) 
	{
		if (! $this->isConnected()) {
			$this->_connect();
		}
		$result = mysql_query($sql, $this->_connection);
		if (false === $result) {
			throw new Exception("Invalid query: {$sql}. Error:" . mysql_error());
		} else {
			return $result;
		}
	}
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#fetchAll()
	 */
	public function fetchAll($sql, $fetchMode = null)
	{
		$list = array();
		if (null === $fetchMode) {
            $fetchMode = $this->_fetchMode;
        }
        
		$result = $this->query($sql);
		while ($row = mysql_fetch_array($result, $fetchMode)) {
			$list[] = $row;
		}
		return $list;
	}
 	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#fetchAllLimited()
	 */
 	public function fetchAllLimited($sql, $limit = null, $offset = null, $fetchMode = null)
 	{
 		$sql = $sql.(($limit===false)?'':(' LIMIT ').(int)$offset.','.(int)$limit);
 		return $this->fetchAll($sql, $fetchMode);
 	}
 	
 	/**
 	 * (non-PHPdoc)
 	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#fetchRow()
 	 */
	public function fetchRow($sql, $fetchMode = null)
	{
		if (null === $fetchMode) {
            $fetchMode = $this->_fetchMode;
        }
        $result = $this->query($sql);
		if ($row = mysql_fetch_array($result, $fetchMode)) {
			return $row;
		} else {
			return array();		
		}
	}
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#fetchRowLimited()
	 */
	public function fetchRowLimited($sql, $limit, $offset, $fetchMode = null)
	{
		$sql = $sql.(($limit===false)?'':(' LIMIT ').(int)$offset.','.(int)$limit);
 		return $this->fetchRow($sql, $fetchMode);
	}
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#fetchOne()
	 */
	public function fetchOne($sql)
	{
        $result = $this->query($sql);
		if ($row = mysql_fetch_row($result)) {
			return $row[0];
		} else {
			return null;		
		}
	}
	
	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#lastInsertId()
	 */
	public function lastInsertId($sequence = null)
	{
		$id = mysql_insert_id($this->_connection);
		if (false === $id) {
			throw new Exception('No database connection was established');
		}
		if (0 === $id) {
			throw new Exception('Previous query does not generate an AUTO_INCREMENT value');
		}	
		return $id;
	}

	/**
	 * (non-PHPdoc)
	 * @see library/Main/Db/Adapter/Main_Db_Adapter_Abstract#escape()
	 */
	public function escape($str, $isQuote = false)
	{
		if (! $this->isConnected()) {
			$this->_connect();
		}
		
		$str = mysql_real_escape_string($str, $this->_connection);
		return ($isQuote) ? "'{$str}'" : $str;
	}
		

}

